import Ad from '_shared/Ad';
import PageMeta from '_shared/PageMeta';

<PageMeta title="Updating to v3" />

## Upgrading to v3

Version `v3` for @material-ui/pickers is coming with a whole bunch of breaking changes. This is a guide of how-to update :)

<Ad />

#### ⬇️ Install

First of all, you need to install the new package, because the project is transferred to mui-org!
Please also note, that **v3** of `@material-ui/pickers` relies on **v4** of `@material-ui/core`

```
npm i @material-ui/pickers @material-ui/core@latest

yarn add @material-ui/pickers @material-ui/core@latest
```

**Note**: It's also required to upgrade your `@material-ui/core` version to `@next`

#### 🌚 Imports

There are a lot of changes in imports. From now on, we are not providing `keyboard` prop on the pickers.
Keyboard mode comes with separate components like `<KeyboardDatePicker />`.
Thus you are assured that keyboard-specific logic will be correctly tree-shaken.

```diff
- import { DatePicker } from '@material-ui/pickers'
+ import { KeyboardDatePicker } from '@material-ui/pickers'

- <DatePicker keyboard />
+ <KeyboardDatePicker />
```

Also there are no more wrapper-specific components, like `InlineDatePicker`. Use `variant` prop instead.

```diff
- import { InlineDatePicker } from '@material-ui/pickers'
+ import { DatePicker } from '@material-ui/pickers'

- <InlineDatePicker />
+ <DatePicker variant="inline" />
```

To override the default material-ui's `<TextField />` variant use

```jsx
<DatePicker variant="inline" inputVariant="outlined" />
```

#### 💪 State management

We have done a lot of work to make state-management of pickers more obvious in `v3` and simplify the form integration experience.
From now on, there is _no hidden internal state_ under the hood. Your components are truly controlled.

That means that now `onChange` will be called on **each** particular day-click or keystroke.
So if you are doing some heavy operations in `onChange` (e.g. xhr requests, dom mutations or redirects) -
please move them to `onAccept`. This callback will be fired only when the user actually accepts the date.

```diff
<DatePicker
+ onChange={setDate} // stateLogic
+ onAccept={requestSomeDataFromServer} // async action
- onChange={(newDate) => {
-   setDate(newDate)
-   requestSomeDataFromServer(newDate)
- }}
/>
```

#### ⌨ Keyboard mode

Previously, keyboard mode was a bit painful, especially from form integration perspective.
That's why we recreated it from scratch.
Now `onChange` prop for `<Keyboard(Date|Time)Picker />` has different signature from the pure pickers:

```ts
type KeybordOnChange = (date: MaterialUiPickersDate | null, value: string | undefined) => void;
```

It is even possible to control keyboard pickers by pure string. ⚠️ `value` prop will work as well ⚠️

```jsx
function KeyboardString() {
  const [value, setValue] = useState('01/01/2019');

  return (
    <KeyboardDatePicker
      format="MM/dd/yyyy"
      inputValue={value}
      onChange={(_, newValue) => setValue(newValue)}
    />
  );
}
```

Also we completely replaced [react-text-mask](https://www.npmjs.com/package/react-text-mask) with [rifm](https://github.com/istarkov/rifm).
That saved us several KBs of bundle size, and improved performance

##### 🎉 And now no more need in mask prop 🎉

Mask will be generated and applied automatically from the `format` passed.
So please, make sure that your formats are easy to input from keyboard.
And it is still possible to fully customize mask, checkout [this](/api/timepicker#keyboard-input) example.

```diff
<KeyboardDatePicker
  format="dd/MM/yyyy"
- mask={[/\d/, /\d/, "/", /\d/, /\d/, "/", /\d/, /\d/, /\d/, /\d/]}
/>
```

#### 🚪 Controlling open/close state

`ref` approach to customize open/close state was replaced with `open` props and `onClose`, `onOpen` callbacks.
Check out the [new example](/guides/controlling-programmatically)

#### 🛡 TypeScript

We are working hard to make this library perfectly TypeScript compatible.
And from `v3` and on, date type in such props like `onChange`, `value` will automatically be inferred from the `@date-io` package you used.
So less `any` from our side :)

#### 🙈 Misc

- Improved accessibility by making the toolbar button actually focusable `<button />`
- Rename `moment` property of `LocalizationProvider` to `libInstance`
- Rename `onlyCalendar` prop to `disableToolbar`
- Remove `withUtils` HOC, and provide `useUtils` hook
- Remove `BasePicker` HOC, and provide `usePickerState` and `useKeyboardPickerState` hooks
- Remove `openToYearSelection` prop in favor of `openTo`
- Remove exported `MuiPickersContextConsumer` in favor of `useUtils` hook
- When using `views` prop - DatePicker by default will open to the the **first** item of `views`.
- Order of views will now follow the order in the passed `views` array.
